/*
 * OVERVIEW:
 * This is a fragment that represents a list of all Agents in our application 
 * using ListView and its features.
 * Fragment is independent of hosting activities because it ensures that each activity
 * to host ManagerFragment must implement its Callback interface.
 */

package sk.stuba.fei.ut.snmpmanager;

import java.util.ArrayList;

import android.app.Activity;
import android.content.Intent;
import android.os.Bundle;
import android.support.v4.app.ListFragment;
import android.view.ActionMode;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AbsListView.MultiChoiceModeListener;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.ListView;
import android.widget.TextView;

public class ManagerFragment extends ListFragment
{
	@SuppressWarnings( "unused" )
	private static final boolean DEBUG = false;
	@SuppressWarnings( "unused" )
	private static final String TAG = "ManagerFragment";
	
	private ArrayList<Agent> mAgents;
	private Button mEmptyButton;
	private Callbacks mCallbacks;

	/*
	 * Interface for hosting activities
	 */
	public interface Callbacks
	{
		void onAgentSelected( Agent agent );
	}

	public void update()
	{
		( ( AgentAdapter ) getListAdapter() ).notifyDataSetChanged();
	}

	/*
	 * #### FRAGMENT LIFE-CYCLE METHODS ####
	 */
	@Override
	public void onAttach( Activity activity )
	{
		super.onAttach( activity );
		// force interface implementation
		try
		{
			mCallbacks = ( Callbacks ) activity;
		}
		catch ( ClassCastException e )
		{
			throw new ClassCastException( activity.toString()
					+ " must implement Callbacks interface" );
		}
	}

	@Override
	public void onDetach()
	{
		super.onDetach();
		mCallbacks = null;
	}

	@Override
	public void onCreate( Bundle savedInstanceState )
	{
		super.onCreate( savedInstanceState );
		setRetainInstance( true );
		setHasOptionsMenu( true );
		getActivity().setTitle( R.string.title );
		// get ArrayList of Agents from AgentManager
		mAgents = AgentManager.get( getActivity() ).getAgents();
		AgentAdapter adapter = new AgentAdapter( mAgents );
		setListAdapter( adapter );
	}

	@Override
	public View onCreateView( LayoutInflater inflater, ViewGroup parent,
			Bundle savedInstanceState )
	{
		View view = inflater.inflate( R.layout.list_agents_and_empty, parent,
				false );

		mEmptyButton = ( Button ) view.findViewById( R.id.empty_button );
		mEmptyButton.setOnClickListener( new View.OnClickListener()
		{

			@Override
			public void onClick( View v )
			{
				// add new agent to AgentManager
				Agent agent = new Agent();
				AgentManager.get( getActivity() ).addAgent( agent );
				// start AgentPagerActivity for result and pass agent id
				Intent i = new Intent( getActivity(), AgentPagerActivity.class );
				i.putExtra( AgentFragment.EXTRA_AGENT_ID, agent.getID() );
				startActivityForResult( i, 0 );
			}
		} );

		// TODO: set up views and their listeners

		ListView listView = ( ListView ) view.findViewById( android.R.id.list );
		listView.setChoiceMode( ListView.CHOICE_MODE_MULTIPLE_MODAL );
		listView.setMultiChoiceModeListener( new MultiChoiceModeListener()
		{
			@Override
			public boolean onPrepareActionMode( ActionMode arg0, Menu arg1 )
			{
				return false;
			}

			@Override
			public void onDestroyActionMode( ActionMode arg0 )
			{
			}

			@Override
			public boolean onCreateActionMode( ActionMode mode, Menu menu )
			{
				MenuInflater inflater = mode.getMenuInflater();
				inflater.inflate( R.menu.agent_list_item_context, menu );
				return true;
			}

			@Override
			public boolean onActionItemClicked( ActionMode mode, MenuItem menu )
			{
				switch ( menu.getItemId() )
				{
				case R.id.menu_item_delete_agent:
					AgentAdapter adapter = ( AgentAdapter ) getListAdapter();
					// delete selected agents from AgentManager
					AgentManager agentManager = AgentManager
							.get( getActivity() );
					for ( int i = adapter.getCount() - 1; i >= 0; i-- )
					{
						if ( getListView().isItemChecked( i ) )
							agentManager.deleteAgent( adapter.getItem( i ) );
					}
					mode.finish();
					adapter.notifyDataSetChanged();
					return true;
				default:
					return false;
				}
			}

			@Override
			public void onItemCheckedStateChanged( ActionMode arg0, int arg1,
					long arg2, boolean arg3 )
			{
			}
		} );
		return view;
	}

	@Override
	public void onResume()
	{
		super.onResume();
		// refresh the list
		( ( AgentAdapter ) getListAdapter() ).notifyDataSetChanged();
	}

	@Override
	public void onCreateOptionsMenu( Menu menu, MenuInflater inflater )
	{
		super.onCreateOptionsMenu( menu, inflater );
		inflater.inflate( R.menu.fragment_manager, menu );
	}

	/*
	 * #### LIST SPECIFICS ####
	 */
	@Override
	public void onListItemClick( ListView l, View v, int position, long id )
	{
		// get position of clicked item and let activity handle
		Agent agent = ( ( AgentAdapter ) getListAdapter() ).getItem( position );
		mCallbacks.onAgentSelected( agent );
	}

	private class AgentAdapter extends ArrayAdapter<Agent>
	{
		public AgentAdapter( ArrayList<Agent> agents )
		{
			// hook up data set of Agents, without layout ( 0 )
			super( getActivity(), 0, agents );
		}

		@Override
		public View getView( int position, View convertView, ViewGroup parent )
		{
			// for performance, DO NOT DELETE
			if ( convertView == null )
			{
				convertView = getActivity().getLayoutInflater().inflate(
						R.layout.list_item_agent, null );
			}

			Agent agent = getItem( position );
			TextView titleTextView = ( TextView ) convertView
					.findViewById( R.id.agent_list_item_titleTextView );
			titleTextView.setText( agent.getTitle() );

			TextView ipPortTextView = ( TextView ) convertView
					.findViewById( R.id.agent_list_item_ipPortTextView );
			ipPortTextView.setText( agent.getIpv4Address() + ":" + agent.getPort() );

			TextView detailTextView = ( TextView ) convertView
					.findViewById( R.id.agent_list_item_detailTextView );
			detailTextView.setText( agent.getDetail() );

			return convertView;
		}
	}

	/*
	 * #### ACTION BAR ####
	 */
	@Override
	public boolean onOptionsItemSelected( MenuItem item )
	{
		switch ( item.getItemId() )
		{
		// TODO: create menus on action bar an hook up reaction on clicks
		case R.id.menu_item_new_agent:
			Agent agent = new Agent();
			AgentManager.get( getActivity() ).addAgent( agent );
			( ( AgentAdapter ) getListAdapter() ).notifyDataSetChanged();
			mCallbacks.onAgentSelected( agent );
			return true;

		default:
			return super.onOptionsItemSelected( item );
		}
	}

}
